package com.nforce.linremote.converters;

import java.nio.ByteBuffer;
import java.security.AlgorithmParameters;
import java.util.Arrays;
import java.util.UUID;

import javax.crypto.Cipher;
import javax.crypto.spec.IvParameterSpec;
import javax.crypto.spec.SecretKeySpec;

public class AESUtils {

    private static byte[] uuidToBytes(String id) {
	UUID uuid = UUID.fromString(id);
	ByteBuffer bb = ByteBuffer.wrap(new byte[16]);
	bb.putLong(uuid.getMostSignificantBits());
	bb.putLong(uuid.getLeastSignificantBits());
	return bb.array();
    }

    public static byte[] encrypt(String key, String data) throws Exception {
	SecretKeySpec skeySpec = new SecretKeySpec(uuidToBytes(key), "AES");
	Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
	cipher.init(Cipher.ENCRYPT_MODE, skeySpec);
	AlgorithmParameters params = cipher.getParameters();
	byte[] iv = params.getParameterSpec(IvParameterSpec.class).getIV();
	byte[] encrypted = cipher.doFinal(data.getBytes("UTF8"));

	ByteBuffer bb = ByteBuffer.wrap(new byte[iv.length + encrypted.length]);
	bb.put(iv);
	bb.put(encrypted);
	return bb.array();
    }

    public static String decrypt(String key, byte[] data) throws Exception {
	SecretKeySpec skeySpec = new SecretKeySpec(uuidToBytes(key), "AES");
	Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");

	byte[] iv = Arrays.copyOfRange(data, 0, 16);
	byte[] encrypted = Arrays.copyOfRange(data, 16, data.length);
	cipher.init(Cipher.DECRYPT_MODE, skeySpec, new IvParameterSpec(iv));
	byte[] decrypted = cipher.doFinal(encrypted);

	return new String(decrypted, "UTF8");
    }

}
